package jwcb.admin.server.dictionary.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import jwcb.admin.api.config.domain.dto.*;
import jwcb.admin.server.dictionary.domain.dto.SysDictionaryDataDto;
import jwcb.admin.server.dictionary.domain.dto.SysDictionaryTypeDto;
import jwcb.admin.server.dictionary.domain.entity.SysDictionaryData;
import jwcb.admin.server.dictionary.domain.entity.SysDictionaryType;
import jwcb.admin.server.dictionary.mapper.SysDictionaryDataMapper;
import jwcb.admin.server.dictionary.mapper.SysDictionaryTypeMapper;
import jwcb.admin.server.dictionary.service.ISysDictionaryService;
import jwcb.javapjframework.common.core.utils.BeanCopyUtil;
import jwcb.javapjframework.common.domain.domain.vo.BasePageVO;
import jwcb.javapjframework.common.domain.exception.ServiceException;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Service
public class SysDictionaryServiceImpl implements ISysDictionaryService {


    @Autowired
    private SysDictionaryTypeMapper sysDictionaryTypeMapper;


    @Autowired
    private SysDictionaryDataMapper sysDictionaryDataMapper;
    /**
     * 新增字典类型
     * @param dictionaryTypeWriteReqDTO 新增数据
     * @return 主键Id
     */
    @Override
    public Long addDictionaryType(DictionaryTypeWriteReqDTO dictionaryTypeWriteReqDTO) {
        SysDictionaryType sysDictionaryType = sysDictionaryTypeMapper.selectOne(new LambdaQueryWrapper<SysDictionaryType>()
                        .select(SysDictionaryType::getId)
                        .eq(SysDictionaryType::getTypeKey, dictionaryTypeWriteReqDTO.getTypeKey())
                        .or()
                        .eq(SysDictionaryType::getValue,dictionaryTypeWriteReqDTO.getValue()));
        if(sysDictionaryType != null) {
            throw new ServiceException("字典类型或者值已经存在");
        }
        sysDictionaryType = new SysDictionaryType();
        sysDictionaryType.setValue(dictionaryTypeWriteReqDTO.getValue());
        sysDictionaryType.setTypeKey(dictionaryTypeWriteReqDTO.getTypeKey());
        if(StringUtils.isNoneBlank(dictionaryTypeWriteReqDTO.getRemark())) {
            sysDictionaryType.setRemark(dictionaryTypeWriteReqDTO.getRemark());
        }
        sysDictionaryTypeMapper.insert(sysDictionaryType);
        return sysDictionaryType.getId();
    }

    /**
     * 字典类型列表查询
     * @param dictionaryTypeListReqDTO 查询信息
     * @return 查询结果
     */

    @Override
    public BasePageVO<SysDictionaryTypeDto> listType(DictionaryTypeListReqDto dictionaryTypeListReqDTO) {
        BasePageVO<SysDictionaryTypeDto> result = new BasePageVO<>();
        LambdaQueryWrapper<SysDictionaryType> queryWrapper = new LambdaQueryWrapper<>();
        if (StringUtils.isNotBlank(dictionaryTypeListReqDTO.getValue())) {
            queryWrapper.likeRight(SysDictionaryType::getValue, dictionaryTypeListReqDTO.getValue());
        }
        if (StringUtils.isNotBlank(dictionaryTypeListReqDTO.getTypeKey())) {
            queryWrapper.eq(SysDictionaryType::getTypeKey, dictionaryTypeListReqDTO.getTypeKey());
        }
        Page<SysDictionaryType> page = sysDictionaryTypeMapper.selectPage(
                new Page<>(dictionaryTypeListReqDTO.getPageNo().longValue(), dictionaryTypeListReqDTO.getPageSize().longValue()),
                queryWrapper
        );
        result.setTotals(Integer.parseInt(String.valueOf(page.getTotal())));
        result.setTotalPages(Integer.parseInt(String.valueOf(page.getPages())));
        List<SysDictionaryTypeDto> list = BeanCopyUtil.copyListProperties(page.getRecords(), SysDictionaryTypeDto::new);
        result.setList(list);
        return result;
    }


    /**
     * 编辑字典类型
     * @param dictionaryTypeWriteReqDTO 编辑信息
     * @return 主键ID
     */
    @Override
    public Long editType(DictionaryTypeWriteReqDTO dictionaryTypeWriteReqDTO) {
        SysDictionaryType sysDictionaryType = sysDictionaryTypeMapper.selectOne(new LambdaQueryWrapper<SysDictionaryType>().eq(SysDictionaryType::getTypeKey, dictionaryTypeWriteReqDTO.getTypeKey()));
        if(sysDictionaryType == null) {
            throw new ServiceException("字典类型不存在");
        }
        if(sysDictionaryTypeMapper.exists(new LambdaQueryWrapper<SysDictionaryType>().ne(SysDictionaryType::getTypeKey,dictionaryTypeWriteReqDTO.getTypeKey()).eq(SysDictionaryType::getValue,dictionaryTypeWriteReqDTO.getValue()))) {
           throw new ServiceException("字典值已经存在");
        }
        sysDictionaryType.setValue(dictionaryTypeWriteReqDTO.getValue());
        sysDictionaryType.setRemark(dictionaryTypeWriteReqDTO.getRemark());
        sysDictionaryTypeMapper.updateById(sysDictionaryType);
        return sysDictionaryType.getId();
    }

    @Override
    public Long addData(DictionaryDataAddReqDTO dictionaryDataAddReqDTO) {
        if (!sysDictionaryTypeMapper.exists(new LambdaQueryWrapper<SysDictionaryType>().eq(SysDictionaryType::getTypeKey,dictionaryDataAddReqDTO.getTypeKey()))) {
            throw new ServiceException("字典类型不存在");
        }
        if(sysDictionaryDataMapper.exists(new LambdaQueryWrapper<SysDictionaryData>().eq(SysDictionaryData::getDataKey,dictionaryDataAddReqDTO.getDataKey()).or().eq(SysDictionaryData::getValue,dictionaryDataAddReqDTO.getValue()))) {
            throw new ServiceException("字典数据键或值已经存在");
        }
        SysDictionaryData sysDictionaryData = new SysDictionaryData();
        BeanCopyUtil.copyProperties(dictionaryDataAddReqDTO,sysDictionaryData);
        sysDictionaryDataMapper.insert(sysDictionaryData);
        return sysDictionaryData.getId();
    }

    /**
     * 根据字典类型和值查询字典数据
     * @param dictionaryDataListReqDTO 查询信息
     * @return 查询结果
     */
    @Override
    public BasePageVO<SysDictionaryDataDto> getDirectoryDataList(DictionaryDataListReqDTO dictionaryDataListReqDTO) {
        BasePageVO<SysDictionaryDataDto> result = new BasePageVO<>();
        LambdaQueryWrapper<SysDictionaryData> queryWrapper = new LambdaQueryWrapper<>();
        if(StringUtils.isBlank(dictionaryDataListReqDTO.getTypeKey())) {
            throw new ServiceException("字典类型不能为空");
        }
        queryWrapper.like(SysDictionaryData::getTypeKey, dictionaryDataListReqDTO.getTypeKey());
        if (StringUtils.isNotBlank(dictionaryDataListReqDTO.getValue())) {
            queryWrapper.likeRight(SysDictionaryData::getValue, dictionaryDataListReqDTO.getValue());
        }
        queryWrapper.orderByAsc(SysDictionaryData::getSort);
        queryWrapper.orderByAsc(SysDictionaryData::getId);
        Page<SysDictionaryData> page = sysDictionaryDataMapper.selectPage(
                new Page<>(dictionaryDataListReqDTO.getPageNo().longValue(), dictionaryDataListReqDTO.getPageSize().longValue()),
                queryWrapper
        );
        result.setTotals(Integer.parseInt(String.valueOf(page.getTotal())));
        result.setTotalPages(Integer.parseInt(String.valueOf(page.getPages())));
        List<SysDictionaryDataDto> list = BeanCopyUtil.copyListProperties(page.getRecords(), SysDictionaryDataDto::new);
        result.setList(list);
        return result;
    }


    /**
     * 编辑字典数据
     * @param dictionaryDataEditReqDTO 编辑内容
     * @return 主键Id
     */
    @Override
    public Long editData(DictionaryDataEditReqDTO dictionaryDataEditReqDTO) {
        SysDictionaryData sysDictionaryData = sysDictionaryDataMapper.selectOne(new LambdaQueryWrapper<SysDictionaryData>().eq(SysDictionaryData::getDataKey, dictionaryDataEditReqDTO.getDataKey()));
        if (sysDictionaryData == null) {
            throw new ServiceException("字典数据键不存在");
        }
        if (sysDictionaryDataMapper.exists(new LambdaQueryWrapper<SysDictionaryData>().ne(SysDictionaryData::getDataKey,dictionaryDataEditReqDTO.getDataKey()).eq(SysDictionaryData::getValue,dictionaryDataEditReqDTO.getValue()))) {
            throw new ServiceException("字典数据值已经存在");
        }
        sysDictionaryData.setValue(dictionaryDataEditReqDTO.getValue());
        sysDictionaryData.setRemark(dictionaryDataEditReqDTO.getRemark());
        sysDictionaryData.setSort(dictionaryDataEditReqDTO.getSort());
        sysDictionaryDataMapper.updateById(sysDictionaryData);
        return sysDictionaryData.getId();
    }


    /**
     * 获取某个字典类型下的所有字典数据
     * @param typeKey 字典类型键
     * @return 字典数据列表
     */
    @Override
    public List<SysDictionaryDataDto> selectDictDataByType(String typeKey) {
        List<SysDictionaryData> sysDictionaryData = sysDictionaryDataMapper.selectList(new LambdaQueryWrapper<SysDictionaryData>().eq(SysDictionaryData::getTypeKey, typeKey));
        return BeanCopyUtil.copyListProperties(sysDictionaryData, SysDictionaryDataDto::new);
    }


    /**
     * 获取多个字典类型下的所有字典数据
     * @param typeKeys 字典类型键列表
     * @return 字典数据列表
     */
    @Override
    public Map<String, List<SysDictionaryDataDto>> selectDictDataByTypeKeys(List<String> typeKeys) {
        List<SysDictionaryData> sysDictionaryData = sysDictionaryDataMapper.selectList(new LambdaQueryWrapper<SysDictionaryData>()
                .in(SysDictionaryData::getTypeKey, typeKeys));
        List<SysDictionaryDataDto> result = BeanCopyUtil.copyListProperties(sysDictionaryData, SysDictionaryDataDto::new);
        return result.stream().collect(Collectors.groupingBy(SysDictionaryDataDto::getTypeKey));
    }


    /**
     * 根据dataKey获取字典数据
     * @param dataKey 字典数据键
     * @return 字典数据
     */
    @Override
    public SysDictionaryDataDto selectDictDataByDataKey(String dataKey) {
        SysDictionaryData sysDictionaryData = sysDictionaryDataMapper.selectOne(new LambdaQueryWrapper<SysDictionaryData>().eq(SysDictionaryData::getDataKey, dataKey));
        if(sysDictionaryData != null) {
            SysDictionaryDataDto sysDictionaryDataDto = new SysDictionaryDataDto();
            BeanCopyUtil.copyProperties(sysDictionaryData, sysDictionaryDataDto);
            return sysDictionaryDataDto;

        }
        return null;
    }


    /**
     * 根据多个dataKey获取字典数据
     * @param dataKeys 字典数据键列表
     * @return 字典数据
     */
    @Override
    public List<SysDictionaryDataDto> selectDictDataByDataKeys(List<String> dataKeys) {
        List<SysDictionaryData> sysDictionaryData = sysDictionaryDataMapper.selectList(new LambdaQueryWrapper<SysDictionaryData>()
                .in(SysDictionaryData::getDataKey, dataKeys));
        return BeanCopyUtil.copyListProperties(sysDictionaryData, SysDictionaryDataDto::new);
    }
}
